package chat

import (
	"encoding/json"
	"errors"
	"time"

	netpack "im/im_server/proto"
	"strconv"

	"github.com/go-redis/redis/v9"
	"google.golang.org/protobuf/proto"
)

type CreateRoomMessageLogic struct {
	chatServer *ChatServer
	redisCmd   *RedisCmd
}

// get room_name 查询room_id
// hscan room_id 迭代查询所有房间简介信息
// sscan room_id 迭代查询所有房间成员信息
// smembers player_id 查询玩家的房间列表信息
// 创建房间流程
func (ch *CreateRoomMessageLogic) CreateRoomProcess(csCreateChatRoom *netpack.CSCreateChatRoom, c *Connection) (int64, error) {
	roomIdIncrby, err := ch.redisCmd.GetRedisIncrByValue(ctx, ServerID+IncrbyRoomIdStr)
	if err != nil {
		return -1, err
	}

	err = ch.redisCmd.SetNXRedisRoomNameValue(ctx, ServerID+HashKeyRoomNameStr,
		ServerID+strconv.FormatInt(roomIdIncrby, 10))
	if err != nil {
		return -1, err
	}

	dbPlayerChatRoom := &netpack.DBPlayerChatRoom{
		RoomId: roomIdIncrby,
	}

	jsonPlayerChatRoomData, err := json.Marshal(dbPlayerChatRoom)
	if err != nil {
		return -1, err
	}

	dbChatRoomMember := &netpack.DBChatRoomMember{
		JoinChatRoomTime:    time.Now().Unix(),
		JoinChatRoomTimeStr: time.Now().Format("2006-01-02 15:04:05"),
		PlayerId:            c.player.PlayerId,
		MemberInfo:          "",
	}

	jsonChatRoomMemberData, err := json.Marshal(dbChatRoomMember)
	if err != nil {
		return -1, err
	}

	dbChatRoomData := &netpack.DBChatRoom{
		CreateRoomTime:    time.Now().Unix(),
		CreateRoomTimeStr: time.Now().Format("2006-01-02 15:04:05"),
		RoomInfo:          csCreateChatRoom.RoomInfo,
		RoomName:          csCreateChatRoom.RoomName,
	}

	jsonChatRoomData, err := json.Marshal(dbChatRoomData)
	if err != nil {
		return -1, err
	}

	// Execute
	//
	// MULTI
	// SADD room_id DBChatRoomMember
	// SADD player_id DBPlayerChatRoom
	// HSetNX room_id filed DBChatRoom
	// EXEC
	//

	err = ch.redisCmd.TxPipielineRedisRoomValue(ctx,
		ServerID+SetKeyRoomIdStr+strconv.FormatInt(roomIdIncrby, 10), string(jsonChatRoomMemberData), // sadd
		ServerID+SetKeyPlayerIdStr+strconv.FormatInt(c.player.PlayerId, 10), string(jsonPlayerChatRoomData), // sadd
		ServerID+HashKeyRoomIdStr+strconv.FormatInt(roomIdIncrby, 10), ServerID+HashfiledRoomIdStr, string(jsonChatRoomData)) // hsetnx
	if err != nil {
		return -1, err
	}
	return roomIdIncrby, nil
}

func (ch *CreateRoomMessageLogic) CreateChatRoom(msg proto.Message, c *Connection) error {
	csCreateChatRoom, ok := msg.(*netpack.CSCreateChatRoom)
	if !ok {
		return errors.New("parse create_charroom message error")
	}

	_, err := ch.redisCmd.GetRedisRoomNameValue(ctx, ServerID+HashKeyRoomNameStr)
	if err != nil && err != redis.Nil {
		return err
	}

	if err == redis.Nil {
		roomId, err := ch.CreateRoomProcess(csCreateChatRoom, c)
		if err != nil {
			return err
		}

		scCreateChatRoom := &netpack.SCCreateChatRoom{
			Error:  netpack.ErrCode_SUCCESS,
			RoomId: roomId,
		}
		return c.reply(netpack.MessageID_SC_CREATE_CHATROOM, scCreateChatRoom)
	} else {
		scCreateChatRoom := &netpack.SCCreateChatRoom{
			Error:  netpack.ErrCode_CHAT_ROOM_EXIST,
			RoomId: -1,
		}
		return c.reply(netpack.MessageID_SC_CREATE_CHATROOM, scCreateChatRoom)
	}
}
